<template>
  <div ref="wrapperRef" class="flex-col-stretch gap-16px overflow-hidden lt-sm:overflow-auto">
    <!-- 搜索表单区域 -->
    <ClassifySearch v-model:model="queryDto" @reset="resetData" @search="searchSysRole" />
    
    <!-- 表格区域 -->
    <ElCard class="sm:flex-1-hidden card-wrapper" body-class="ht50">
      <template #header>
        <div class="flex items-center justify-between">
          <p>分类管理</p>
          <ElButton type="primary" size="small" @click="InsertTJ()">添加</ElButton>
        </div>
      </template>

      <!-- 懒加载的树形表格 -->
      <div class="h-[calc(100%-50px)]">
        <ElTable
          :data="list"
          height="100%"
          border
          class="sm:h-full"
          row-key="id"
          lazy
          :load="fetchData"
          :tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
        >
          <ElTableColumn prop="categoryName" label="分类名称" />
          <ElTableColumn prop="orderNum" label="排序" />
          <ElTableColumn prop="status" label="状态" #default="scope">
            {{ scope.row.status == 1 ? '正常' : '停用' }}
          </ElTableColumn>
          <ElTableColumn prop="createTime" label="创建时间" />
          <ElTableColumn label="操作" align="center" width="300" #default="scope">
            <div class="flex-center justify-center gap-8px">
              <ElButton type="primary" plain size="small" @click="Insert(scope.row)">添加子目录</ElButton>
              <ElButton type="warning" plain size="small" @click="Update(scope.row)">编辑</ElButton>
              <ElPopconfirm title="确定要删除该分类吗？" @confirm="deleteById(scope.row)">
                <template #reference>
                  <ElButton type="danger" plain size="small">删除</ElButton>
                </template>
              </ElPopconfirm>
            </div>
          </ElTableColumn>
        </ElTable>
        <div class="mt-20px flex justify-end">
          <ElPagination
            v-if="list.length"
            layout="total,prev,pager,next,sizes"
            :total="list.length"
          />
        </div>
      </div>
    </ElCard>
  </div>

  <!-- 对话框 -->
  <ElDialog v-model="dialogVisible" :title="dialogTitle" width="30%">
    <ElForm label-width="120px">
      <ElFormItem label="分类名称">
        <ElInput v-model="sysMenu.categoryName"/>
      </ElFormItem>
      <ElFormItem v-if="!sysMenu.hasChildren" label="上级部门" prop="categoryId">
        <ElTreeSelect
          v-model="sysMenu.categoryId"
          :data="deptOptions"
          :props="{ value: 'id', label: 'name', isLeaf: 'leaf' }"
          :load="loadNode"
          lazy
          @visible-change="handleVisibleChange"
          value-key="id"
          placeholder="选择上级部门"
          check-strictly/>
      </ElFormItem>
      <ElFormItem label="排序">
        <ElInputNumber v-model="sysMenu.orderNum" :min="0" :max="100" />
      </ElFormItem>
      <ElFormItem label="状态">
        <ElRadioGroup v-model="sysMenu.status">
          <ElRadio :label="1">正常</ElRadio>
          <ElRadio :label="0">停用</ElRadio>
        </ElRadioGroup>
      </ElFormItem>
      <ElFormItem>
        <ElButton type="primary" @click="submit">提交</ElButton>
        <ElButton @click="dialogVisible = false">取消</ElButton>
      </ElFormItem>
    </ElForm>
  </ElDialog>
</template>

<script setup>
import { ref, onMounted } from 'vue';
import { ElMessage, ElMessageBox, ElButton, ElPopconfirm } from 'element-plus';
import { PictureById, findAll, SavePicture, UpdatePicture, RemovePicture } from '@/service/api/material/classify';
import ClassifySearch from './modules/classify-search.vue';


// 定义list属性模型
const list = ref([]);

// 查询参数
const queryDto = ref({
  categoryName: '',
  status: -1
});

// 搜索方法
const searchSysRole = () => {
  zy();
}

// 重置查询条件
const resetData = () => {
  queryDto.value = {
    categoryName: '',
    status: -1
  };
  zy();
}

const deptOptions = ref([]);

const dialogVisible = ref(false)
const dialogTitle = ref('')

const sysMenu = ref({
id: "",
categoryName: "",
status: 1,
orderNum: 1,
categoryId: "",
hasChildren:""
})

// 页面初始化完毕以后请求后端接口查询数据
onMounted(() => {

zy();
})

const zy = async () => {
  // 构建查询参数
  const params = {};
  if (queryDto.value.categoryName) {
    params.categoryName = queryDto.value.categoryName;
  }
  if (queryDto.value.status !== -1) {
    params.status = queryDto.value.status;
  }
  
  const { code, data, message } = await findAll(params);
  list.value = data; // 更新表格数据
};

const isLoaded = ref(false); // 标志位，确保数据只加载一次
// 当下拉框显示/隐藏时触发
const handleVisibleChange = async (visible) => {
if (visible && !isLoaded.value) {
    try {
      const res = await PictureById(0);
      deptOptions.value = res.data.map(item => ({
        id: item.id,
        name: item.categoryName,
        leaf: !item.hasChildren
      }));
      isLoaded.value = true; // 标记为已加载
    } catch (error) {
          console.error("加载数据失败:", error);
        }
      }
};

// 懒加载子节点
const loadNode = async (node, resolve) => {
  if (node.level === 0) {
    return resolve(deptOptions.value);
  }

  try {
    const parentId = node.data.id;
    const res = await PictureById(parentId);
    const nodes = res.data.map(item => ({
      id: item.id,
      name: item.categoryName,
      leaf: !item.hasChildren
    }));
    resolve(nodes);
  } catch (error) {
    console.error("加载子节点失败:", error);
    resolve([]); // 返回空数组，避免页面卡死
  }
};

// 加载数据的方法
const fetchData = async (row, treeNode, resolve) => {
const { code, data, message } = await PictureById(row.id)
resolve(data)
}

// 图像上传成功以后的事件处理函数
const handleAvatarSuccess = (response, uploadFile) => {
sysMenu.value.imageUrl = response.data
}

// 提交表单数据
const submit = async () => {
  try {
    let result;
    // 根据ID判断是新增还是修改
    if (!sysMenu.value.id) {
      result = await SavePicture(sysMenu.value);
    } else {
      result = await UpdatePicture(sysMenu.value);
    }
    
    const { code, message } = result;
    
    if (code === 200) {
      dialogVisible.value = false;
      ElMessage.success('操作成功');
      // 刷新数据
      await zy();
    } else {
      ElMessage.error(message || '操作失败');
    }
  } catch (error) {
    console.error('提交数据出错:', error);
    ElMessage.error('操作失败，请稍后重试');
  }
}
}

// 删除分类
const deleteById = async (row) => {
  try {
    const { code, message } = await RemovePicture(row.id);
    if (code === 200) {
      ElMessage.success('删除成功');
      await zy(); // 刷新数据
    } else {
      ElMessage.error(message || '删除失败');
    }
  } catch (error) {
    console.error('删除数据出错:', error);
    ElMessage.error('删除失败，请稍后重试');
  }
}


// 修改数据
const Update = async(row) => {
  try {
    // 处理上级分类ID
    row.categoryId = row.categoryId === 0 ? null : row.categoryId;
    
    // 加载分类选项
    if (row.categoryId != 0) {
      const res = await PictureById(0);
      deptOptions.value = res.data.map(item => ({
        id: item.id,
        name: item.categoryName,
        leaf: !item.hasChildren
      }));
      isLoaded.value = true; // 标记为已加载
    }
    
    // 设置表单数据并显示对话框
    sysMenu.value = {...row};
    dialogVisible.value = true;
    dialogTitle.value = "修改";
  } catch (error) {
    console.error('加载编辑数据出错:', error);
    ElMessage.error('加载数据失败，请稍后重试');
  }
}


// 添加顶级分类
const InsertTJ = () => {
  // 重置表单数据
  sysMenu.value = {
    id: "-99",
    categoryName: "",
    categoryId: "",
    status: 1,
    orderNum: 1,
    hasChildren: true
  };
  
  // 显示对话框
  dialogVisible.value = true;
  dialogTitle.value = "添加";
}
// 添加子分类
const Insert = async(row) => {
  try {
    // 加载分类选项
    const res = await PictureById(row.categoryId);
    deptOptions.value = res.data.map(item => ({
      id: item.id,
      name: item.categoryName,
      leaf: !item.hasChildren
    }));
    isLoaded.value = true; // 标记为已加载
    
    // 设置表单数据
    sysMenu.value = {
      id: "",
      categoryName: "",
      categoryId: row.id,
      status: 1,
      orderNum: 1
    };
    
    // 显示对话框
    dialogVisible.value = true;
    dialogTitle.value = "添加";
  } catch (error) {
    console.error('加载添加数据出错:', error);
    ElMessage.error('加载数据失败，请稍后重试');
  }
}
</script>

<style lang="scss" scoped>
:deep(.el-card) {
  .ht50 {
    height: calc(100% - 50px);
  }
}

.flex-center {
  display: flex;
  align-items: center;
}

.justify-end {
  justify-content: flex-end;
}

.pr-10px {
  padding-right: 10px;
}

.mt-20px {
  margin-top: 20px;
}

.mb-16px {
  margin-bottom: 16px;
}
</style>